using JGSY.CMS.LowCode.Platform.Application.DTOs;
using Microsoft.AspNetCore.Http;
using System.Collections.Generic;
using System.Threading.Tasks;

namespace JGSY.CMS.LowCode.Platform.Application.Interfaces
{
    /// <summary>
    /// 媒体文件应用服务接口
    /// 提供媒体文件管理相关的业务逻辑操作
    /// </summary>
    public interface IMediaFileAppService
    {
        /// <summary>
        /// 获取所有媒体文件
        /// </summary>
        /// <returns>媒体文件列表</returns>
        Task<IEnumerable<MediaFileDto>> GetAllAsync();

        /// <summary>
        /// 根据ID获取媒体文件
        /// </summary>
        /// <param name="id">媒体文件ID</param>
        /// <returns>媒体文件信息</returns>
        Task<MediaFileDto?> GetByIdAsync(long id);

        /// <summary>
        /// 根据文件路径获取媒体文件
        /// </summary>
        /// <param name="filePath">文件路径</param>
        /// <returns>媒体文件信息</returns>
        Task<MediaFileDto?> GetByFilePathAsync(string filePath);

        /// <summary>
        /// 根据哈希值获取媒体文件
        /// </summary>
        /// <param name="hash">哈希值</param>
        /// <returns>媒体文件信息</returns>
        Task<MediaFileDto?> GetByHashAsync(string hash);

        /// <summary>
        /// 根据分类获取媒体文件
        /// </summary>
        /// <param name="category">文件分类</param>
        /// <returns>媒体文件列表</returns>
        Task<IEnumerable<MediaFileDto>> GetByCategoryAsync(string category);

        /// <summary>
        /// 根据文件类型获取媒体文件
        /// </summary>
        /// <param name="fileType">文件类型</param>
        /// <returns>媒体文件列表</returns>
        Task<IEnumerable<MediaFileDto>> GetByFileTypeAsync(string fileType);

        /// <summary>
        /// 分页获取媒体文件列表
        /// </summary>
        /// <param name="pageIndex">页码</param>
        /// <param name="pageSize">页大小</param>
        /// <param name="keyword">搜索关键词</param>
        /// <param name="category">文件分类</param>
        /// <param name="fileType">文件类型</param>
        /// <param name="status">状态过滤</param>
        /// <returns>分页媒体文件列表</returns>
        Task<(IEnumerable<MediaFileDto> Items, int TotalCount)> GetPagedAsync(
            int pageIndex, 
            int pageSize, 
            string? keyword = null, 
            string? category = null,
            string? fileType = null,
            byte? status = null);

        /// <summary>
        /// 上传文件
        /// </summary>
        /// <param name="file">上传的文件</param>
        /// <param name="category">文件分类</param>
        /// <param name="title">文件标题</param>
        /// <param name="description">文件描述</param>
        /// <param name="alt">替代文本</param>
        /// <returns>上传的媒体文件信息</returns>
        Task<MediaFileDto> UploadAsync(
            IFormFile file, 
            string? category = null,
            string? title = null,
            string? description = null,
            string? alt = null);

        /// <summary>
        /// 批量上传文件
        /// </summary>
        /// <param name="files">上传的文件列表</param>
        /// <param name="category">文件分类</param>
        /// <returns>上传的媒体文件信息列表</returns>
        Task<IEnumerable<MediaFileDto>> BatchUploadAsync(
            IEnumerable<IFormFile> files, 
            string? category = null);

        /// <summary>
        /// 创建媒体文件记录
        /// </summary>
        /// <param name="mediaFileDto">媒体文件信息</param>
        /// <returns>创建的媒体文件</returns>
        Task<MediaFileDto> CreateAsync(MediaFileDto mediaFileDto);

        /// <summary>
        /// 更新媒体文件信息
        /// </summary>
        /// <param name="mediaFileDto">媒体文件信息</param>
        /// <returns>更新的媒体文件</returns>
        Task<MediaFileDto> UpdateAsync(MediaFileDto mediaFileDto);

        /// <summary>
        /// 删除媒体文件
        /// </summary>
        /// <param name="id">媒体文件ID</param>
        /// <param name="deletePhysicalFile">是否删除物理文件</param>
        /// <returns>是否删除成功</returns>
        Task<bool> DeleteAsync(long id, bool deletePhysicalFile = true);

        /// <summary>
        /// 批量删除媒体文件
        /// </summary>
        /// <param name="ids">媒体文件ID列表</param>
        /// <param name="deletePhysicalFiles">是否删除物理文件</param>
        /// <returns>删除的数量</returns>
        Task<int> BatchDeleteAsync(IEnumerable<long> ids, bool deletePhysicalFiles = true);

        /// <summary>
        /// 更新媒体文件状态
        /// </summary>
        /// <param name="id">媒体文件ID</param>
        /// <param name="status">状态</param>
        /// <returns>是否更新成功</returns>
        Task<bool> UpdateStatusAsync(long id, byte status);

        /// <summary>
        /// 增加下载次数
        /// </summary>
        /// <param name="id">媒体文件ID</param>
        /// <returns>是否更新成功</returns>
        Task<bool> IncrementDownloadCountAsync(long id);

        /// <summary>
        /// 生成缩略图
        /// </summary>
        /// <param name="id">媒体文件ID</param>
        /// <param name="width">缩略图宽度</param>
        /// <param name="height">缩略图高度</param>
        /// <returns>缩略图URL</returns>
        Task<string?> GenerateThumbnailAsync(long id, int width = 150, int height = 150);

        /// <summary>
        /// 搜索媒体文件
        /// </summary>
        /// <param name="keyword">搜索关键词</param>
        /// <param name="pageIndex">页码</param>
        /// <param name="pageSize">页大小</param>
        /// <returns>搜索结果</returns>
        Task<(IEnumerable<MediaFileDto> Items, int TotalCount)> SearchAsync(
            string keyword, 
            int pageIndex = 1, 
            int pageSize = 20);

        /// <summary>
        /// 获取存储统计信息
        /// </summary>
        /// <returns>存储统计信息</returns>
        Task<object> GetStorageStatisticsAsync();

        /// <summary>
        /// 清理未使用的文件
        /// </summary>
        /// <returns>清理的文件数量</returns>
        Task<int> CleanupUnusedFilesAsync();

        /// <summary>
        /// 验证文件格式
        /// </summary>
        /// <param name="file">文件</param>
        /// <param name="allowedTypes">允许的文件类型</param>
        /// <returns>验证结果</returns>
        Task<bool> ValidateFileAsync(IFormFile file, string[]? allowedTypes = null);

        /// <summary>
        /// 获取文件访问URL
        /// </summary>
        /// <param name="id">媒体文件ID</param>
        /// <param name="expireMinutes">过期时间（分钟）</param>
        /// <returns>访问URL</returns>
        Task<string?> GetFileUrlAsync(long id, int? expireMinutes = null);
    }
}
